package LAAMI;

import repast.simphony.engine.environment.RunEnvironment;

public class BlackScholes {

	private static double maturity;

	private static double timeUntilExpiration;

	// /**
	// * Prices European style options using the Black-Scholes formula.
	// * @param call true for call options, false for puts
	// * @param S the price of the underlying
	// * @param K the strike of the option
	// * @param T the time to expiration, in years
	// * @param r the risk free interest rate
	// * @param v the volatility
	// * @return the Black-Scholes option price
	// */
	public static double getPrice(boolean call, double S, double K, double v) {
		double d1, d2;
		timeUntilExpiration = calculateTime();
		double r = LAAMIBuilder.getInterestRate();
		double sqrtT = Math.sqrt(timeUntilExpiration);
		double vsqrtT = v * sqrtT;
		double price;

		d1 = (Math.log(S / K) + (r + v * v / 2) * timeUntilExpiration) / vsqrtT;
		d2 = d1 - vsqrtT;

		if (call)
			price = S * N(d1) - K * Math.exp(-r * timeUntilExpiration) * N(d2);
		else
			price = K * Math.exp(-r * timeUntilExpiration) * N(-d2) - S
					* N(-d1);

		return price;
	}

	public static double N(double X) {
		double L, K, w;
		double a1 = 0.31938153, a2 = -0.356563782, a3 = 1.781477937, a4 = -1.821255978, a5 = 1.330274429;

		L = Math.abs(X);
		K = 1.0 / (1.0 + 0.2316419 * L);
		w = 1.0
				- 1.0
				/ Math.sqrt(2.0 * Math.PI)
				* Math.exp(-L * L / 2)
				* (a1 * K + a2 * K * K + a3 * Math.pow(K, 3) + a4
						* Math.pow(K, 4) + a5 * Math.pow(K, 5));

		if (X < 0.0)
			w = 1.0 - w;
		return w;
	}

	public static double calculateTime() {
		maturity = LAAMIBuilder.getMaturity();
		double day = RunEnvironment.getInstance().getCurrentSchedule()
				.getTickCount();
		return (maturity - (day - 50) / 252);
	}

	public static double getTimeUntilExpiration() {
		return timeUntilExpiration;
	}

	public static void setTimeUntilExpiration(double t) {
		timeUntilExpiration = t;
	}

	public static double getMaturity() {
		return maturity;
	}

	public static void setMaturity(double maturity) {
		BlackScholes.maturity = maturity;
	}
}
